import { ObjResettingWithEvent } from "earthsdk3";
import { Destroyable, HasOwner, react, reactJson } from "earthsdk3";
import { MyProjectManager } from "../MyProjectManager";
import {
  reqGetMonomer,
  reqGetMonomerProperty,
  reqGetShpFeatures,
  reqUpdateMonomer,
  reqUploadShp,
  reqUploadShpZip,
  reqGetInstanceList,
} from "@/api/modelser2Api";
import { ESGeoExtrudedPolygonUFMS } from "../esobjs/ESGeoExtrudedPolygonUFMS";
import { ElMessage } from "element-plus";
import { ESClassification } from "earthsdk3";
import { processNum } from "@/scripts/utils";

class PickResettting extends Destroyable {
  constructor(monomerEdit: MonomerEdit, owner: MyProjectManager) {
    super();
    const viewer = owner.activeViewer;
    if (!viewer) return;

    this.dispose(
      viewer.clickEvent.don(async (e) => {
        if (!e.screenPosition) return;
        // 拾取

        let obj: any;
        if (viewer.typeName == "ESCesiumViewer") {
          // @ts-ignore
          obj = await viewer.quickPickPosition(e.screenPosition);
        } else {
          obj = await viewer.pickPosition(e.screenPosition);
        }

        // 编辑页面打开
        if (monomerEdit.isShow) return;
        // 单体化信息
        const info = await monomerEdit.getMonomer(obj);

        if (!info || !Object.entries(info).length) {
          // 修改了的单体化属性
          monomerEdit.changedMonomerProperty = {};
          monomerEdit.monomerProperty = [];
          monomerEdit.monomerInfo = {};
          monomerEdit.eSClassification.points = [];
          return;
        }

        // 单体化属性
        monomerEdit.monomerProperty = monomerEdit.propertyLists.map(
          (item: any) => {
            return {
              key: item.name,
              type: item.type,
              value: info[item.name],
            };
          }
        );

        // 单体化信息
        monomerEdit.monomerInfo = {
          id: info.id,
          name: info.name,
          bottom: info.minh,
          ceilling: info.maxh,
          points: JSON.parse(info.geojson).coordinates[0],
        };

        // 设置es单体化对象 点位 高度
        const points = JSON.parse(info.geojson).coordinates[0].slice(0, -1);
        const i = points.findIndex(
          (e: any) => e[2] == Math.min(...points.map((item: any) => item[2]))
        );
        monomerEdit.eSClassification.points = [
          ...points.slice(i),
          ...points.slice(0, i),
        ];
        monomerEdit.eSClassification.height = info.maxh - info.minh;
        monomerEdit.eSClassification.fillStyle = {
          color: [0, 0, 1, 0.5],
          material: "",
          materialParams: {},
          ground: true,
        };
      })
    );
  }
}

class PickResettting2 extends Destroyable {
  constructor(monomerEdit: MonomerEdit, owner: MyProjectManager) {
    super();
    const viewer = owner.activeViewer;
    if (!viewer) return;

    this.dispose(
      viewer.clickEvent.don(async (e) => {
        if (!e.screenPosition) return;
        // 拾取
        const res = await viewer.pick(e.screenPosition);
        if (!res || !res.tilesetPickInfo) {
          monomerEdit.monomerProperty = [];
          monomerEdit.currentId = "";
          return;
        }

        console.log("res", res);

        // 单体化属性
        monomerEdit.monomerProperty = Object.entries(res.tilesetPickInfo)
          .map((item: any) => {
            const type = monomerEdit.propertyLists.find(
              (e: any) => e.name === item[0]
            )?.type;
            return {
              key: item[0],
              type: type,
              value: item[1],
            };
          })
          .filter((e: any) => e.type);
        const maxh = monomerEdit.monomerProperty.find((e: any) => e.key === "maxh")
        maxh.value = processNum(maxh.value)
        const minh = monomerEdit.monomerProperty.find((e: any) => e.key === "minh")
        minh.value = processNum(minh.value)
        monomerEdit.currentId = monomerEdit.monomerProperty.find(
          (e: any) => e.key === "id"
        )?.value;
      })
    );
  }
}

export class MonomerEdit extends HasOwner<MyProjectManager> {
  // 开启拾取
  private _enablePick = this.dv(react<boolean>(false));
  get enablePick() {
    return this._enablePick.value;
  }
  get enablePickChanged() {
    return this._enablePick.changed;
  }
  set enablePick(value: boolean) {
    this._enablePick.value = value;
  }

  // 选中的单体化id
  private _currentId = this.dv(react<string>(""));
  get currentId() {
    return this._currentId.value;
  }
  get currentIdChanged() {
    return this._currentId.changed;
  }
  set currentId(value: string) {
    this._currentId.value = value;
  }

  // 是否显示编辑页面
  private _isShow = this.dv(react<boolean>(false));
  get isShow() {
    return this._isShow.value;
  }
  get isShowChanged() {
    return this._isShow.changed;
  }
  set isShow(value: boolean) {
    this._isShow.value = value;
  }

  // 单体化信息
  private _monomerInfo = this.dv(reactJson<any>({}));
  get monomerInfo() {
    return this._monomerInfo.value;
  }
  get monomerInfoChanged() {
    return this._monomerInfo.changed;
  }
  set monomerInfo(value: any) {
    this._monomerInfo.value = value;
  }

  // 单体化属性
  private _monomerProperty = this.dv(reactJson<any>([]));
  get monomerProperty() {
    return this._monomerProperty.value;
  }
  get monomerPropertyChanged() {
    return this._monomerProperty.changed;
  }
  set monomerProperty(value: any) {
    this._monomerProperty.value = value;
  }

  // 单体化属性
  private _instanceList = this.dv(reactJson<any>([]));
  get instanceList() {
    return this._instanceList.value;
  }
  get instanceListChanged() {
    return this._instanceList.changed;
  }
  set instanceList(value: any) {
    this._instanceList.value = value;
  }

  // 修改了的单体化属性
  private _changedMonomerProperty = this.dv(reactJson<any>({}));
  get changedMonomerProperty() {
    return this._changedMonomerProperty.value;
  }
  get changedMonomerPropertyChanged() {
    return this._changedMonomerProperty.changed;
  }
  set changedMonomerProperty(value: any) {
    this._changedMonomerProperty.value = value;
  }

  // 所有的单体化属性列表
  private _propertyLists = this.dv(reactJson<any>([]));
  get propertyLists() {
    return this._propertyLists.value;
  }
  get propertyListsChanged() {
    return this._propertyLists.changed;
  }
  set propertyLists(value: any) {
    this._propertyLists.value = value;
  }

  // 单体化
  private _eSClassification = this.dv(
    this.owner.createSceneObject(ESClassification) as ESClassification
  );
  get eSClassification() {
    return this._eSClassification;
  }

  // 拾取处理
  private _pickResettting = this.dv(
    new ObjResettingWithEvent(this.enablePickChanged, () => {
      if (!this.enablePick) return undefined;
      return new PickResettting2(this, this.owner);
    })
  );
  get pickResettting() {
    return this._pickResettting;
  }

  get eSMsTileset() {
    return this.owner.modelser2Manager.eSMsTileset;
  }

  // 根据经纬度获取单体化
  async getMonomer(position: [number, number, number]) {
    try {
      const param = {
        tileSerivceName: this.eSMsTileset.tileServiceName,
        position: position,
      };
      const res = await reqGetMonomer(param);
      // @ts-ignore
      if (res.status != "ok" || !res.data) return [];
      return res.data;
    } catch (error) {
      console.error(error);
    }
  }

  // 获取单体化属性列表
  async getMonomerProperty() {
    try {
      const param = {
        tileSerivceName: this.eSMsTileset.tileServiceName,
      };
      const res = await reqGetMonomerProperty(param);
      // @ts-ignore
      if (res.status != "ok" || !res.data) return [];
      this.propertyLists = res.data.data;
    } catch (error) {
      console.error(error);
    }
  }



  // 修改单体化
  async updateMonomer(param: any) {
    try {
      const res = await reqUpdateMonomer(param);
      // @ts-ignore
      if (res.status != "ok") return;
      ElMessage({
        message: "修改单体化成功",
        type: "success",
      });
      this.monomerProperty = [];
      this.changedMonomerProperty = {};
      this.monomerInfo = {};
      this.isShow = false;
      this.eSClassification.points = [];
    } catch (error) {
      console.error(error);
    }
  }

  // 上传shp
  async uploadShp(param: any) {
    try {
      const res = await reqUploadShp(param);
      // @ts-ignore
      if (res.code != 1000) return "";
      ElMessage({
        message: "上传成功",
        type: "success",
      });
      return res.data;
    } catch (error) {
      console.error(error);
    }
  }

  // 上传shp(zip格式)
  async uploadShpZip(param: any) {
    try {
      const res = await reqUploadShpZip(param);
      // @ts-ignore
      if (res.code != 1000) return "";
      ElMessage({
        message: "上传成功",
        type: "success",
      });
      return res.data;
    } catch (error) {
      console.error(error);
    }
  }

  // 获取shp中所有要素
  async getShpFeatures(param: any) {
    try {
      const res = await reqGetShpFeatures(param);
      // @ts-ignore
      if (res.code != 1000) return [];
      return res.data;
    } catch (error) {
      console.error(error);
    }
  }

  async init() {
    await this.getMonomerProperty();
    this.enablePick = true;
  }
  clear() {
    this.enablePick = false;
    this.monomerProperty = [];
    this.changedMonomerProperty = {};
    this.monomerInfo = {};
    this.isShow = false;
    this.eSClassification.points = [];
    this.currentId = "";
  }

  constructor(owner: MyProjectManager) {
    super(owner);

    {
      const updata = (newVal: string, oldVal: string) => {
        if (oldVal) {
          const json = [
            {
              value: oldVal,
              rgba: [1, 1, 1, 1],
            },
          ] as any;
          this.eSMsTileset.setFeatureColor("id", json);
        }
        if (newVal) {
          const json = [
            {
              value: newVal,
              rgba: [0, 0, 1, 1],
            },
          ] as any;
          this.eSMsTileset.setFeatureColor("id", json);
        }
      };
      this.dispose(this.currentIdChanged.don(updata));
    }
  }
}
